from typing import Callable


def dichotomy(equation: Callable[[float], float], left: float, right: float, delta: float = 1E-9) -> float:
    if delta < 0:
        delta = -delta

    def close_to_zero(value: float) -> int:
        if -delta < value < delta:
            return 0
        return 1 if value > 0 else -1

    left_sign = close_to_zero(equation(left))
    if left_sign == 0:
        return left

    right_sign = close_to_zero(equation(right))
    if right_sign == 0:
        return right

    if left_sign == right_sign:
        raise ValueError("不合适的区间")

    mid = (left + right) / 2
    mid_sign = close_to_zero(equation(mid))

    return dichotomy(equation, mid, right, delta) if left_sign == mid_sign\
        else dichotomy(equation, left, mid, delta)


def _main():
    def equation(x: float):
        return 2 * (x ** 3) - 4 * (x ** 2) + 3 * x - 6

    delta = 1E-16
    print(f"其解为 x = {dichotomy(equation, -10, 10, delta=delta)} (±{delta}) 。")


if __name__ == "__main__":
    _main()
